package com.wugh.fast.module.mapper;

import cn.hutool.core.exceptions.ExceptionUtil;
import com.alibaba.fastjson.JSON;
import com.wugh.fast.kernel.core.props.MapperProperties;
import com.wugh.fast.kernel.core.util.SpringContextHolder;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import tk.mybatis.mapper.entity.EntityTable;
import tk.mybatis.mapper.entity.IDynamicTableName;
import tk.mybatis.mapper.mapperhelper.EntityHelper;

import javax.persistence.Transient;
import java.util.Optional;

/**
 * 说明:
 *
 * @author wugh
 * @date 2018-12-03 08:55
 */
@Slf4j
public abstract class DynamicSchema implements IDynamicTableName {
    /**
     * mapper配置
     */
    @Transient
    private static MapperProperties mapperProperties;
    /**
     * 动态表名
     */
    @Transient
    private String tableName4Dynamic;

    @Override
    public String getDynamicTableName() {
        String schema = getDynamicSchema();
        if (StringUtils.isBlank(schema)) {
            return getTableName4Dynamic();
        }
        String tableName4Dynamic = getTableName4Dynamic();
        if (tableName4Dynamic.contains(".")) {
            //已有schema,替换schema
            //替换一次 public.user -> schema.user
            tableName4Dynamic = tableName4Dynamic.substring(tableName4Dynamic.indexOf(".") + 1);
        }
        tableName4Dynamic = schema + "." + tableName4Dynamic;
        return getMapperProperties().getLowerTable() ? tableName4Dynamic.toLowerCase() : tableName4Dynamic;

    }

    protected String getTableName4Dynamic() {
        if (tableName4Dynamic == null) {
            synchronized (this) {
                if (tableName4Dynamic == null) {
                    Class<?> clazz = this.getClass();
                    do {
                        try {
                            EntityTable entityTable = EntityHelper.getEntityTable(clazz);
                            tableName4Dynamic = getMapperProperties().getLowerTable() ? entityTable.getName().toLowerCase() : entityTable.getName();

                        } catch (Exception e) {
                            //捕获到异常即当前类不是数据库的实体类,取上级继续找
                            clazz = clazz.getSuperclass();
                        }
                    } while (tableName4Dynamic == null && clazz != null);
                }
            }
        }
        return tableName4Dynamic;
    }

    protected static MapperProperties getMapperProperties() {
        if (mapperProperties == null) {
            try {
                mapperProperties = SpringContextHolder.getBean(MapperProperties.class);
            } catch (Exception e) {
                log.warn("Mapper配置报错:{}", ExceptionUtil.getRootCauseMessage(e));
                mapperProperties = new MapperProperties();
                log.warn("Mapper配置使用默认值:{}", JSON.toJSONString(mapperProperties));
            }
        }
        return mapperProperties;
    }

    public String getDynamicSchema() {
        //获取schame,并且把小写
        Optional<String> optional = Optional.ofNullable(DynamicSchemaStorage.get());
        if (getMapperProperties().getLowerTable()) {
            optional.map(String::toLowerCase);
        }
        return optional.orElse(null);
    }
}
